package com.shuyangyang.structure;

/**
 * 自己实现线性表结构，顺序数组
 *
 * @author shuyangyang
 * @version 1.0.0
 * @date 2020-3-28 13:30:24
 */
public class MyArrayList<T> implements MyList<T> {

    // 数组初始化容量为10
    private static final int DEFAULT_CAPACITY = 10;

    /**
     * 使用一个数组来实现当前ArrayList
     */
    private Object[] elementData;

    /**
     * 数组里的元素个数
     */
    private int size;

    MyArrayList() {
        size = 0;
        elementData = new Object[DEFAULT_CAPACITY];
    }

    @Override
    public int size() {
        return size;
    }

    @Override
    public boolean isEmpty() {
        return this.size() == 0;
    }

    @Override
    public void add(T element) {
        this.add(size, element);
    }

    @Override
    public void add(int index, T element) {
        // 如果当前数组元素个数超过数组最大容量，那么需要扩容
        if (this.size >= elementData.length) {
            Object[] oldElementData = elementData;
            // 新数组扩容量为旧数组的2倍
            elementData = new Object[oldElementData.length * 2];
            // 声明一个新数组，将旧数组的值按顺序填充进来
            for (int i = 0; i < size(); i++) {
                elementData[i] = oldElementData[i];
            }
        }

        // 如果数组从中间某一位置添加元素，那么数组后面元素需要整体后移
        if (index != size) {
            for (int j = size; j > index; j--) {
                elementData[j] = elementData[j - 1];
            }
        }

        // 继续向数组后面追加元素
        elementData[index] = element;
        // 指针向后移动1位
        size++;
    }

    @Override
    public T get(int index) {
        if (this.isEmpty()) {
            return null;
        }
        if (index < 0 || index > elementData.length) {
            throw new MyArrayIndexOutOfBoundsException("数组越界异常：" + index);
        }
        return (T) elementData[index];
    }

    @Override
    public void remove(int index) {
        // 删除类似中间插入，删除一个数，那么数组后面的元素向前移动，size减一

        if (index < 0 || index > elementData.length) {
            throw new MyArrayIndexOutOfBoundsException("数组越界异常：" + index);
        }

        for (int i = index; i < elementData.length - 1; i++) {
            elementData[i] = elementData[i+1];
        }

        // 指针向前移动1位
        size--;
    }

    @Override
    public String listToString() {
        StringBuilder stringBuilder = new StringBuilder("[");
        if (this.isEmpty()) {
            return "[]";
        }
        for (int i = 0; i < size; i++) {
            stringBuilder.append(elementData[i]);
            stringBuilder.append(" ");
        }
        stringBuilder.append("]");
        return stringBuilder.toString();
    }
}
